package dframe.ranger.client;

import java.util.ArrayList;
import java.util.Collection;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.ws.rs.core.MediaType;

import org.apache.ranger.admin.client.datatype.RESTResponse;
import org.apache.ranger.plugin.model.RangerPolicy;
import org.apache.ranger.plugin.util.RangerRESTUtils;
import org.apache.ranger.plugin.util.ServicePolicies;

import com.google.gson.Gson;
import com.google.gson.GsonBuilder;
import com.sun.jersey.api.client.Client;
import com.sun.jersey.api.client.ClientResponse;
import com.sun.jersey.api.client.GenericType;
import com.sun.jersey.api.client.WebResource;
import com.sun.jersey.api.client.filter.HTTPBasicAuthFilter;

import dframe.ranger.client.model.VXGroup;
import dframe.ranger.client.model.VXUser;
import dframe.ranger.client.model.VXUserGroupInfo;

public class DframeRangerPolicyClient {
	
	private static final String EXPECTED_MIME_TYPE = "application/json";
	private static final String RANGER_REPOS_URL = "http://192.168.0.177:6080";

	/**
	 * Get Policy by service-name and policy-name
	 */
	public static void testGetPolicy() {
		String url = RANGER_REPOS_URL + "/service/public/v2/api/service/hadoopdev/policy/kms-audit-path";

		Client client = null;
		ClientResponse response = null;
		try {  
	        client = Client.create();
	        client.addFilter(new HTTPBasicAuthFilter("admin", "admin"));  
            WebResource webResource = client.resource(url);  
            response = webResource.accept(EXPECTED_MIME_TYPE).get(ClientResponse.class);  
            if(response.getStatus() == 200) {  
                String jsonString = response.getEntity(String.class);  
                System.out.println(jsonString);  
            }  
        } finally {  
            if(response != null) {  
                response.close();  
            }
            if(client != null) {  
                client.destroy();  
            }  
        }  
    }

	public static void testDownload() {
		String url = RANGER_REPOS_URL + "/service/plugins/policies/download/hivedev";  
  
        ClientResponse response = null;  
        Client client = null;  
        try {  
            client = Client.create();  
            WebResource webResource = client.resource(url)  
                    .queryParam(RangerRESTUtils.REST_PARAM_LAST_KNOWN_POLICY_VERSION, Long.toString(68))  
                    .queryParam(RangerRESTUtils.REST_PARAM_PLUGIN_ID, "aaa");  
            response = webResource.accept(RangerRESTUtils.REST_MIME_TYPE_JSON).get(ClientResponse.class);  
  
            if (response != null && response.getStatus() == 200) {  
                ServicePolicies ret = response.getEntity(ServicePolicies.class);  
                System.out.println(ret);  
            } else if (response != null && response.getStatus() == 304) {  
                // no change  
            	System.out.println("aaaaaaaaa");  
            } else {  
                RESTResponse resp = RESTResponse.fromClientResponse(response);  
            }  
        } finally {  
            if(response != null) {  
                response.close();  
            }  
            if(client != null) {  
                client.destroy();  
            }  
        }  
    }  
  
    private static RangerPolicy policyBlongToHive() {  
        RangerPolicy rangerPolicy = new RangerPolicy();  
        rangerPolicy.setService("hive-dev");  
        rangerPolicy.setName("project-all-path");  
        rangerPolicy.setIsAuditEnabled(true);  
  
        Map<String, RangerPolicy.RangerPolicyResource> resources = new HashMap<>();  
  
        RangerPolicy.RangerPolicyResource rangerPolicyResource = new RangerPolicy.RangerPolicyResource();  
        rangerPolicyResource.setIsExcludes(false);  
        rangerPolicyResource.setIsRecursive(true);  
        rangerPolicyResource.setValue("*");  
  
        resources.put("database", rangerPolicyResource);  
        resources.put("table", rangerPolicyResource);  
        resources.put("column", rangerPolicyResource);  
  
        List<RangerPolicy.RangerPolicyItem> policyItems = new ArrayList<>();  
  
        RangerPolicy.RangerPolicyItem rangerPolicyItem = new RangerPolicy.RangerPolicyItem();  
        List<String> users = new ArrayList<>();  
        users.add("zune");  
        rangerPolicyItem.setUsers(users);  
  
        List<RangerPolicy.RangerPolicyItemAccess> rangerPolicyItemAccesses = new ArrayList<>();  
        RangerPolicy.RangerPolicyItemAccess rangerPolicyItemAccess = new RangerPolicy.RangerPolicyItemAccess();  
        rangerPolicyItemAccess.setType("select");  
        rangerPolicyItemAccess.setIsAllowed(Boolean.TRUE);  
        rangerPolicyItemAccesses.add(rangerPolicyItemAccess);  
  
        rangerPolicyItem.setAccesses(rangerPolicyItemAccesses);  
  
        policyItems.add(rangerPolicyItem);  
  
        rangerPolicy.setPolicyItems(policyItems);  
        rangerPolicy.setResources(resources);  
        return rangerPolicy;  
    }
    
    private static RangerPolicy policyBlongToHdfs() {  
        RangerPolicy rangerPolicy = new RangerPolicy();  
        rangerPolicy.setService("hadoopdev");  
        rangerPolicy.setName("mx_test_-1267765743_ALL");  
        rangerPolicy.setIsAuditEnabled(true); 
        rangerPolicy.setPolicyType(0);
        rangerPolicy.setDescription("/mx_test/input ALL");
  
        Map<String, RangerPolicy.RangerPolicyResource> resources = new HashMap<>();  
  
        RangerPolicy.RangerPolicyResource rangerPolicyResource = new RangerPolicy.RangerPolicyResource();  
        rangerPolicyResource.setIsExcludes(false);  
        rangerPolicyResource.setIsRecursive(true);  
        rangerPolicyResource.setValue("/mx_projects/mx_test/input");  
  
        resources.put("path", rangerPolicyResource);  
  
        List<RangerPolicy.RangerPolicyItem> policyItems = new ArrayList<>();  
  
        RangerPolicy.RangerPolicyItem rangerPolicyItem = new RangerPolicy.RangerPolicyItem();  
        List<String> users = new ArrayList<>();  
        rangerPolicyItem.setUsers(users);
        
        List<String> userGroups = new ArrayList<String>();
//        userGroups.add("public");
//        userGroups.add("hadoop");
        rangerPolicyItem.setGroups(userGroups);
  
        List<RangerPolicy.RangerPolicyItemAccess> rangerPolicyItemAccesses = new ArrayList<>();  
        RangerPolicy.RangerPolicyItemAccess rangerPolicyItemAccess = new RangerPolicy.RangerPolicyItemAccess();  
        rangerPolicyItemAccess.setType("read");  
        rangerPolicyItemAccess.setIsAllowed(Boolean.TRUE);  
        rangerPolicyItemAccesses.add(rangerPolicyItemAccess);  
  
        rangerPolicyItem.setAccesses(rangerPolicyItemAccesses);  
  
        policyItems.add(rangerPolicyItem);  
  
        rangerPolicy.setPolicyItems(policyItems);  
        rangerPolicy.setResources(resources);
        
        return rangerPolicy;  
    }
    
    /**
     * Create Policy
     */
    public static void testCreatePolicy() {  
  
        String url = RANGER_REPOS_URL + "/service/public/v2/api/policy";  
  
        ClientResponse response = null;  
        Client client = null;  
        try {  
            client = Client.create();  
            client.addFilter(new HTTPBasicAuthFilter("admin", "admin"));
  
            WebResource webResource = client.resource(url); 
  
            Gson gson = new Gson();  
            System.out.println(gson.toJson(policyBlongToHive()));
  
            response = webResource.accept(RangerRESTUtils.REST_EXPECTED_MIME_TYPE)  
                    .type(RangerRESTUtils.REST_EXPECTED_MIME_TYPE)
                    .post(ClientResponse.class, gson.toJson(policyBlongToHive()));
//                    .post(ClientResponse.class, gson.toJson(policyBlongToHdfs()));  
  
            if (response != null && response.getStatus() == 200) {
            	System.out.println(response.toString());
                RangerPolicy ret = response.getEntity(RangerPolicy.class);  
                System.out.println(ret);  
            } else {  
                System.out.println(response.getStatus());  
            } 
        }catch(Exception ex) {
        	ex.printStackTrace();
        } finally {  
            if(response != null) {  
                response.close();  
            }  
            if(client != null) {  
                client.destroy();  
            }  
        }  
  
    }  
  
    public static void testUpdatePolicy() {  
  
        String url = RANGER_REPOS_URL + "/service/public/v2/api/policy/11";  
  
        RangerPolicy rangerPolicy = policyBlongToHdfs();  
        rangerPolicy.getPolicyItems().get(0).getUsers().add("june");  
  
  
        ClientResponse response = null;  
        Client client = null;  
        try {  
            client = Client.create();  
            client.addFilter(new HTTPBasicAuthFilter("admin", "admin"));  
  
            WebResource webResource = client.resource(url);  
  
            Gson gson = new Gson();  
  
            response = webResource.accept(RangerRESTUtils.REST_EXPECTED_MIME_TYPE)  
                    .type(RangerRESTUtils.REST_EXPECTED_MIME_TYPE)  
                    .put(ClientResponse.class, gson.toJson(rangerPolicy));  
  
            if (response != null && response.getStatus() == 200) {  
                RangerPolicy ret = response.getEntity(RangerPolicy.class);  
                System.out.print(ret.getId());  
                System.out.println(ret);  
            } else {  
                System.out.println(response.getStatus());  
            }  
        } finally {  
            if(response != null) {  
                response.close();  
            }  
            if(client != null) {  
                client.destroy();  
            }  
        }  
    }  
  
    public static void testDeletepolicy() {  
        String url = RANGER_REPOS_URL + "/service/public/v2/api/policy/29";  
  
  
        ClientResponse response = null;  
        Client client = null;  
        try {  
            client = Client.create();  
            client.addFilter(new HTTPBasicAuthFilter("admin", "admin"));  
  
            WebResource webResource = client.resource(url);  
  
            webResource.accept(RangerRESTUtils.REST_EXPECTED_MIME_TYPE).delete();  
  
        } finally {  
            if(response != null) {  
                response.close();  
            }  
            if(client != null) {  
                client.destroy();  
            }  
        }  
    }
    
    public static void testLoadPolicy() {  
        String url = RANGER_REPOS_URL + "/service/public/v2/api/service/hive-dev/policy";  
  
  
        ClientResponse response = null;  
        Client client = null;  
        try {  
            client = Client.create();  
            client.addFilter(new HTTPBasicAuthFilter("admin", "admin"));  
  
            WebResource webResource = client.resource(url)
            		.queryParam("resource:database", "test_admin")
                    .queryParam("pageSize", Long.toString(68))  
                    .queryParam("startIndex", Long.toString(0));
  
            response = webResource.accept(EXPECTED_MIME_TYPE).get(ClientResponse.class);  
            if(response.getStatus() == 200) { 
                RangerPolicy[] policyList = response.getEntity(new GenericType<RangerPolicy[]>(){});
                
                for(RangerPolicy policy : policyList) {
                	System.out.println(policy);  
                }
            }   
        } finally {  
            if(response != null) {  
                response.close();  
            }  
            if(client != null) {  
                client.destroy();  
            }  
        }  
    }
    
    
	public static void main(String[] args) {
		testLoadPolicy();
//		testCreateGroup();
		
//		testGetUser();
//		testGetGroup();
		
//		testGetUserGroupInfo();
		
//		testCreateUserGroupInfo();
//		testCreatePolicy();
//		testGetPolicy();
		
//		testUpdatePolicy();
		
	}

}
